package com.cy.store.service.impl;

import com.cy.store.entity.User;
import com.cy.store.repository.UserRepository;
import com.cy.store.service.IUserService;
import com.cy.store.service.ex.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.DigestUtils;

import java.util.Date;
import java.util.UUID;

//@Service：将当前类对象交给Spring来管理，自动创建对象以及对象的维护
@Service
public class UserServiceImpl implements IUserService {

    @Autowired
    UserRepository userRepository;

    @Override
    public void reg(User user) {
//        调用findByUsername(String name)判断用户是否被注册过
        User result = userRepository.findByUsername(user.getUsername());
//        通过判断result是否null来决定抛出用户名被占用异常
        if(result!=null){
//            抛出异常
            throw new UsernameDuplicateException("用户名被占用");
        }

//        加密的作用是：防止拿到数据库后，直接知道密码
//        加密处理，md5算法的形式：67dndsgh-yeuwrey121-yerui374-yrwirei-67123
//        串 + password + 串 ———— md5算法加密，连续加载三次
//        盐值 + password + 盐值  ————  盐值是随机字符串
        String oldPassword = user.getPassword();
//        随机生成的盐值
        String salt = UUID.randomUUID().toString().toUpperCase();
//        将密码和盐值作为一个整体加密处理
        String md5Password = getMD5Password(oldPassword, salt);
        user.setPassword(md5Password);

//        数据补全
        user.setSalt(salt);
        user.setIsDelete(0);
        user.setCreatedUser(user.getUsername());
        user.setCreatedTime(new Date());
        user.setModifiedUser(user.getUsername());
        user.setModifiedTime(new Date());


//        无异常则执行注册功能，判断注册是否成功
        User res = userRepository.save(user);
        if(res == null){
            throw new InsertException("注册失败");
        }
    }

    @Override
    public User login(String username, String password) {
        //根据用户名查询用户数据是否存在
        User user = userRepository.findByUsername(username);
        if(user==null)
            throw new UserNotFoundException("用户数据不存在");

        //密码匹配
        //先获取数据库中的密码,盐值,然后将password与盐值进行加密,再比对
        String MD5Password = getMD5Password(password, user.getSalt());
        if(!user.getPassword().equals(MD5Password))
            throw  new PasswordNotMatchException("用户密码错误");

        //判断数据是否被删除
        if(user.getIsDelete() == 1)
            throw new UserNotFoundException("用户数据不存在");

        //返回以供其他页面做数据展示
        //只需要三个属性,优化
        User res = new User();
        res.setUid(user.getUid());
        res.setUsername(user.getUsername());
        res.setAvatar(user.getAvatar());
        return res;
    }

    @Override
    public void changePassword(Integer uid, String oldPassword, String newPassword) {
        //根据uid查找对象，解决UserNotFoundException异常
        User user = userRepository.findById(uid).orElseThrow(()->new UserNotFoundException("用户数据不存在"));
        if(user == null) throw new UserNotFoundException("用户数据不存在");
        //检查is_delete=1，判断数据是否删除
        if(user.getIsDelete().equals(1)) throw new UserNotFoundException("用户数据不存在");

        //检验旧密码，解决PasswordNotMatchException异常
        String oldMd5Password = getMD5Password(oldPassword, user.getSalt());
        if(!user.getPassword().contentEquals(oldMd5Password)) throw new PasswordNotMatchException("原密码错误");

        //修改密码，根据成功与否，解决UpdateException异常
        String newMd5Password = getMD5Password(newPassword, user.getSalt());
        user.setPassword(newMd5Password);
        user.setModifiedUser(user.getUsername());
        user.setModifiedTime(new Date());
        if(userRepository.save(user)==null)
            throw new UpdateException("插入异常");
    }

    @Override
    public User getById(Integer uid) {
        User user = userRepository.findById(uid).orElseThrow(()->new UserNotFoundException("用户数据不存在"));
        if(user == null) throw new UserNotFoundException("用户数据不存在");
        //检查is_delete=1，判断数据是否删除
        if(user.getIsDelete().equals(1)) throw new UserNotFoundException("用户数据不存在");
        return user;
    }

    @Override
    public void changeInfo(Integer uid, User obj) {
        //提取出对象
        User user = userRepository.findById(uid).orElseThrow(()->new UserNotFoundException("用户数据不存在"));
        if(user == null) throw new UserNotFoundException("用户数据不存在");
        //检查is_delete=1，判断数据是否删除
        if(user.getIsDelete().equals(1)) throw new UserNotFoundException("用户数据不存在");

        //补全数据：电话+邮箱+性别
        //修改人+修改时间
        user.setPhone(obj.getPhone());
        user.setEmail(obj.getEmail());
        user.setGender(obj.getGender());
        user.setModifiedUser(user.getUsername());
        user.setModifiedTime(new Date());
        if(userRepository.save(user)==null)
            throw new UpdateException("修改异常");

    }

    @Override
    public void changeAvatar(Integer uid, String avatar) {
        //查人，UserNotFoundException异常
        User user = userRepository.findById(uid).orElseThrow(()->new UserNotFoundException("用户数据不存在"));
        if(user == null) throw new UserNotFoundException("用户数据不存在");
        //检查is_delete=1，判断数据是否删除
        if(user.getIsDelete().equals(1)) throw new UserNotFoundException("用户数据不存在");

        //修改，UpdateException异常
        Integer rows = userRepository.updateAvatarByUid(uid,avatar,user.getUsername(),new Date());
        if(rows!=1){
            throw new UpdateException("更新数据时候发生错误");
        }
    }

    //md5加密算法
    private String getMD5Password(String password, String salt){
        for(int i=0; i<3; i++)
            password = DigestUtils.md5DigestAsHex((salt+password+salt).getBytes()).toUpperCase();
//        返回加密后的密码
        return password;
    }

}
